"""
:synopsis: Export to ZIP
:authors: Riley Baird (OK), Emma Baker (OK)

"""
import os
import re
from pathlib import Path

import arcpy

from ng911ok.lib.misc import unwrap_to_dict, unwrap
from ng911ok.lib.gdbsession import NG911Session


class ExportToZipTool:
    """
    Class describing an ArcGIS Python Toolbox tool: "Export to ZIP".
    """

    def __init__(self):
        """Define the tool (tool name is the name of the class)."""
        self.label = "Export to Zip"
        self.description = ""
        self.canRunInBackground = False
        self.category = "6 - Submission"

    def getParameterInfo(self):
        """Define parameter definitions"""
        params = [
            arcpy.Parameter(
                displayName="NG911 Geodatabase",
                name="gdb",
                datatype="DEWorkspace",
                parameterType="Required",
                direction="Input"
            ),
            arcpy.Parameter(
                displayName="Output ZIP File",
                name="output_zip_file",
                datatype="DEFile",
                parameterType="Required",
                direction="Output",
            ),
            arcpy.Parameter(
                displayName="Respect Submit",
                name="respect_submit",
                datatype="GPBoolean",
                parameterType="Optional",
                direction="Input"
            ),
            arcpy.Parameter(
                displayName="Overwrite Existing Output",
                name="overwrite",
                datatype="GPBoolean",
                parameterType="Optional",
                direction="Input"
            )
        ]
        return params

    def isLicensed(self):
        """Set whether tool is licensed to execute."""
        return True

    def updateParameters(self, parameters):
        """Modify the values and properties of parameters before internal
        validation is performed.  This method is called whenever a parameter
        has been changed."""
        param_dict: dict[str, arcpy.Parameter] = {p.name: p for p in parameters}
        param_values = unwrap_to_dict(parameters)
        gdb_path = Path(x) if (x := param_values["gdb"]) else None
        out_file_param = param_dict["output_zip_file"]
        if gdb_path and not out_file_param.altered:
            # Compute default value for output_zip_file if gdb parameter has been set
            param_dict["output_zip_file"].value = str(gdb_path.parent / f"{gdb_path.name}.zip")
        if out_file_param.altered:
            if "." not in unwrap(out_file_param):
                out_file_param.value += ".gdb.zip"

    def updateMessages(self, parameters):
        """Modify the messages created by internal validation for each tool
        parameter.  This method is called after internal validation."""
        param_dict: dict[str, arcpy.Parameter] = {p.name: p for p in parameters}
        param_values = unwrap_to_dict(parameters)
        if (out_file_param := param_dict["output_zip_file"]).altered:
            out_file = unwrap(out_file_param) or ""
            if os.path.exists(out_file) and not param_values["overwrite"]:
                out_file_param.setIDMessage("ERROR", 2869, out_file)
            elif not out_file.endswith(".gdb.zip"):
                if out_file.endswith(".zip") or out_file.endswith(".gdb"):
                    out_file_param.value = re.sub(r"\.(zip|gdb)$", ".gdb.zip", out_file)
                else:
                    out_file_param.setErrorMessage("File path must end in '.gdb.zip'.")

    def execute(self, parameters, messages):
        """The source code of the tool."""
        param_dict: dict[str, arcpy.Parameter] = {p.name: p for p in parameters}
        param_values = unwrap_to_dict(parameters)
        gdb = Path(param_values["gdb"])
        output_zip_file = Path(param_values["output_zip_file"])
        respect_submit = bool(param_values["respect_submit"])
        overwrite = bool(param_values["overwrite"])

        with NG911Session(gdb, respect_submit, messenger=messages) as session:
            session.export_to_zip(output_zip_file, overwrite=overwrite)

if __name__ == "__main__":
    raise Exception("This module is a dependency of an ArcGIS Python Toolbox and should not be executed directly.")
